﻿
namespace Bettzueche.RLLibrary.Types
{
    /// <summary>
    /// Q- und e-Wert zu einem Zustads-Aktions-Paar.
    /// </summary>
    public struct WETupel
    {
        /// <summary>
        /// Gibt den Gewichtungswert (q-Wert).
        /// </summary>
        public double W;

        /// <summary>
        /// Gibt den Lohnberechtungswert (eligibility-Wert)
        /// </summary>
        public double E;

        /// <summary>
        /// Initializes a new instance of the <see cref="WETupel"/> class.
        /// </summary>
        /// <param name="gewicht">The Gewicht (q-Wert).</param>
        /// <param name="berechtigung">The berechtigung (e-Wert).</param>
        public WETupel(double gewicht, double berechtigung) {
            W = gewicht;
            E = berechtigung;
        }

        #region objec overrides

        /// <summary>
        /// Returns a hash code for this instance.
        /// </summary>
        /// <returns>
        /// A hash code for this instance, suitable for use in hashing algorithms and data structures like a hash table. 
        /// </returns>
        public override int GetHashCode() {
            int hash = 23;
            hash = hash * 37 + W.GetHashCode();
            hash = hash * 37 + E.GetHashCode();
            ;
            return hash;
        }

        /// <summary>
        /// Determines whether the specified <see cref="System.Object" />, is equal to this instance.
        /// </summary>
        /// <param name="obj">The <see cref="System.Object" /> to compare with this instance.</param>
        /// <returns>
        ///   <c>true</c> if the specified <see cref="System.Object" /> is equal to this instance; otherwise, <c>false</c>.
        /// </returns>
        public override bool Equals(object obj) {
            if (obj == null)
                return false;
            if (obj is WETupel) {
                var other = (WETupel)obj;
                return this.Equals(other);
            }
            return false;
        }

        /// <summary>
        /// Determines whether the specified <see cref="WETupel" />, is equal to this instance.
        /// </summary>
        /// <param name="other">The <see cref="WETupel" /> to compare with this instance.</param>
        /// <returns>
        ///   <c>true</c> if the specified <see cref="WETupel" />'s fields are equal to this instance' fields; otherwise, <c>false</c>.
        /// </returns>
        public bool Equals(WETupel other) {
            double diff = this.W - other.W;
            if (diff > 0.000001 || diff < -0.000001)
                return false;
            diff = this.E - other.E;
            if (diff > 0.000001 || diff < -0.000001)
                return false;
            return true;
        }

        /// <summary>
        /// Returns a <see cref="System.String" /> that represents this instance.
        /// </summary>
        /// <returns>
        /// A <see cref="System.String" /> that represents this instance.
        /// </returns>
        public override string ToString() {
            return string.Format("WETupel({0:N3},{1:N3})",W ,E);
        }

        #endregion
    }
}
